home *** CD-ROM | disk | FTP | other *** search
/ PsL Monthly 1993 December / PSL Monthly Shareware CD-ROM (December 1993).iso / prgmming / dos / c / schdate.c < prev    next >
Encoding:
Text File  |  1989-07-29  |  31.5 KB  |  1,080 lines

  1. /*
  2. ==============================================================================
  3. | (c) 1989, SchönSoft & John-Marc C. Arnau       CREATION DATE:  03/05/89    |
  4. |----------------------------------------------------------------------------|
  5. | MODULE: Date-Time Handling                     VERSION: 1.0   REVISION: 2  |
  6. |----------------------------------------------------------------------------|
  7. | COPYRIGHT NOTICE                                                           |
  8. | ================                                                           |
  9. |                                                                            |
  10. | Everyone is permitted to copy and distribute verbatim copies               |
  11. | of this license and source file, but changing it is not allowed.           |
  12. | You can also use this wording to make the terms for other programs.        |
  13. | The license agreements of most software companies keep you at the          |
  14. | mercy of those companies.  By contrast, my license is intended to          |
  15. | give everyone the right to share this source file. To make sure that       |
  16. | you get the rights I want you to have, I need to make restrictions         |
  17. | that forbid anyone to deny you these rights or to ask you to surrender     |
  18. | the rights.  Hence this license agreement.                                 |
  19. |                                                                            |
  20. | Specifically, I want to make sure that you have the right to give          |
  21. | away copies of this source file, that you receive source code or else      |
  22. | can get it if you want it, that you can change this source file or use     |
  23. | pieces of it in new free programs, and that you know you can do these      |
  24. | things.                                                                    |
  25. |                                                                            |
  26. | To make sure that everyone has such rights, I have to forbid you to        |
  27. | deprive anyone else of these rights. For example, if you distribute        |
  28. | copies of this source file, you must give the recipients all the rights    |
  29. | that you have. You must make sure that they, too, receive or can get the   |
  30. | source code. And you must tell them their rights.                          |
  31. |                                                                            |
  32. | Also, for my own protection, I must make certain that everyone             |
  33. | finds out that there is no warranty for this source file. If this source   |
  34. | file is modified by someone else and passed on, I want its recipients      |
  35. | to know that what they have is not what I distributed, so that any problems| 
  36. | introduced by others will not reflect on my reputation.                    |
  37. |                                                                            |
  38. | Therefore I, JOHN-MARC C. ARNAU make the following terms which say what    |
  39. | you must do to be allowed to distribute or change this source file.        |
  40. |                                                                            |
  41. |                                                                            |
  42. |            COPYING POLICIES                                     |
  43. |                                                                            |
  44. | 1. You may copy and distribute verbatim copies of this source code         |
  45. | as you receive it, in any medium, provided that you conspicuously and      |
  46. | appropriately publish on each copy a valid copyright notice "Copyright     |
  47. | (C) 1989 John-Marc C. Arnau." (or with whatever year is appropriate);      |
  48. | keep intact the notices on all files that refer to this License Agreement  |
  49. | and to the absence of any warranty; and give any other recipients of the   |
  50. | source file a copy of this License Agreement along with the program.       |
  51. | You may charge a distribution fee for the physical act of transferring     |
  52. | a copy.                                                                    |
  53. |                                                                            |
  54. | 2. You may modify your copy or copies of this source file or any portion   |
  55. | of it, and copy and distribute such modifications under the terms of       |
  56. | Paragraph 1 above, provided that you also do the following:                |
  57. |                                                                            |
  58. |   a) cause the modified files to carry prominent notices stating           |
  59. |   that you changed the files and the date of any change; and               |
  60. |                                                                            |
  61. |   b) cause the whole of any work that you distribute or publish,           |
  62. |   that in whole or in part contains or is a derivative of this source      |
  63. |   file or any part thereof, to be licensed at no charge to all third       |
  64. |   parties on terms identical to those contained in this License            |
  65. |   Agreement (except that you may choose to grant more extensive            |
  66. |   warranty protection to some or all third parties, at your option).       |
  67. |                                                                            |
  68. |   c) You may charge a distribution fee for the physical act of             |
  69. |   transferring a copy, and you may at your option offer warranty           |
  70. |   protection in exchange for a fee.                                        |
  71. |                                                                            |
  72. |   Mere aggregation of another unrelated program with this program          |
  73. |   (or its derivative) on a volume of a storage or distribution medium      |
  74. |   does not bring the other program under the scope of these terms.         |
  75. |                                                                            |
  76. | 3. You may copy and distribute this source file (or a portion or           |
  77. | derivative of it, under Paragraph 2) in object code or executable form     |
  78. | under the terms of Paragraphs 1 and 2 above provided that you also         |
  79. | do one of the following:                                                   |
  80. |                                                                            |
  81. |   a) accompany it with the complete corresponding machine-readable         |
  82. |   source code, which must be distributed under the terms of                |
  83. |   Paragraphs 1 and 2 above; or,                                            |
  84. |                                                                            |
  85. |   b) accompany it with a written offer, valid for at least three           |
  86. |   years, to give any third party free (except for a nominal                |
  87. |   shipping charge) a complete machine-readable copy of the                 |
  88. |   corresponding source code, to be distributed under the terms of          |
  89. |   Paragraphs 1 and 2 above; or,                                            |
  90. |                                                                            |
  91. |   c) accompany it with the information you received as to where the        |
  92. |   corresponding source code may be obtained.    (This alternative is         |
  93. |   allowed only for noncommercial distribution and only if you              |
  94. |   received the program in object code or executable form alone.)           |
  95. |                                                                            |
  96. | For an executable file, complete source code means all the source code     |
  97. | for all modules it contains; but, as a special exception, it need not      |
  98. | include source code for modules which are standard libraries that          |
  99. | accompany the operating system on which the executable file runs.          |
  100. |                                                                            |
  101. | 4. You may not copy, sublicense, distribute or transfer this source file   |
  102. | except as expressly provided under this License Agreement.  Any attempt    |
  103. | otherwise to copy, sublicense, distribute or transfer this source file     |
  104. | is void and your rights to use the program under this License agreement    |
  105. | shall be automatically terminated.  However, parties who have received     |
  106. | computer software programs from you with this License Agreement will       |
  107. | not have their licenses terminated so long as such parties remain in       |
  108. | full compliance.                                                           |
  109. |                                                                            |
  110. | 5. If you wish to incorporate parts of this source file into other         |
  111. | free programs whose distribution conditions are different, write to        |
  112. | John-Marc C. Arnau, P.O. Box 14208  08080-BARCELONA (Cathalonia) EUROPE,   |
  113. | or else EMAIL me at Compuserve Nº 70441,2164. I will be guided by the      |
  114. | two goals of preserving the free status of all derivatives of my free      |
  115. | software and of promoting the sharing and reuse of software.               |
  116. |                                                                            |
  117. | Your comments and suggestions about my licensing policies and my           |
  118. | software are welcome!  Please contact the John-Marc C. Arnau,              |
  119. | P.O. Box 14208  08080-BARCELONA (Cathalonia) EUROPE, or else EMAIL me at   |
  120. | Compuserve Nº 70441,2164.                                                  |
  121. |                                                                            |
  122. |                        NO WARRANTY                                   |
  123. |                                                                            |
  124. | BECAUSE THIS SOURCE FILE IS LICENSED FREE OF CHARGE, I PROVIDE ABSOLUTELY  |
  125. | NO WARRANTY, TO THE EXTENT PERMITTED BY APPLICABLE INTERNATIONAL LAW.EXCEPT|
  126. | WHEN OTHERWISE STATED IN WRITING, JOHN-MARC C. ARNAU AND/OR OTHER PARTIES  |
  127. | PROVIDE THIS SOURCE "AS IS" WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESSED |
  128. | OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF       |
  129. | MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK AS   | 
  130. | TO THE QUALITY AND PERFORMANCE OF THIS SOURCE FILE IS WITH YOU.  SHOULD    |
  131. | THIS SOURCE PROVE DEFECTIVE, YOU ASSUME THE COST OF ALL NECESSARY SERVICING, 
  132. | REPAIR OR CORRECTION.                                                      |
  133. |                                                                            |
  134. | IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW WILL JOHN-MARC C. ARNAU      |
  135. | AND/OR ANY OTHER PARTY WHO MAY MODIFY AND REDISTRIBUTE THIS SOURCE FILE    |
  136. | AS PERMITTED ABOVE, BE LIABLE TO YOU FOR DAMAGES, INCLUDING ANY LOST       |
  137. | PROFITS, LOST MONIES, OR OTHER SPECIAL, INCIDENTAL OR CONSEQUENTIAL        |
  138. | DAMAGES ARISING OUT OF THE USE OR INABILITY TO USE (INCLUDING BUT NOT      |
  139. | LIMITED TO LOSS OF DATA OR DATA BEING RENDERED INACCURATE OR LOSSES        |
  140. | SUSTAINED BY THIRD PARTIES OR A FAILURE OF THE PROGRAM TO OPERATE WITH     |
  141. | ANY OTHER PROGRAMS) THIS SOURCE FILE, EVEN IF YOU HAVE BEEN ADVISED OF     |
  142. | THE POSSIBILITY OF SUCH DAMAGES, OR FOR ANY CLAIM BY ANY OTHER PARTY.      |
  143. |                                                                            |
  144. | This copyright notice has been modified from R. Stallman & FREE SOFTWARE   |
  145. | FOUNDATION, INC. general public license.                                   |
  146. |                                                                            |
  147. | NAME                                                                       |
  148. |   SHÖN DATE-TIME HANDLING SYSTEM                REF: 001-890727            |
  149. |                                                                            |
  150. | DESCRIPTION                                                                |
  151.  
  152.     Many of you have probably got into trouble trying to cope with
  153. dates and times while hoping to bring a nice piece of programming to
  154. life. So have I. That's why I have set up this tiny date-time handling
  155. system. There was a particular point that woried me:  should I use UNIX(R)
  156. like date-time internal representation or, else, should I move to a
  157. standard that would handle my grandfather's birthdate ?. Finnaly I decided
  158. to implement both, and in the end I've got a code full of conditional
  159. compilation commands. It works anyway !!!.
  160.  
  161.     COMPILATION HINTS
  162.     =================
  163.  
  164.     This code has been developed and tested under Turbo C 2.0
  165. compiler. Let's hope it will run under any ANSI compatible C compiler
  166. with a proper standard library. By the way, I hate C compilers without 
  167. function prototyping. Don't you ?.
  168.  
  169.     The only thing you have to care abouth when compiling this file
  170. is getting the proper definitions according to your own needs:
  171.  
  172.     1) LANGUAGE:
  173.  
  174.     You can choose between: ENGLISH, CATHALAN AND SPANISH. No doubt 
  175. there's room for many others if you have the time to implement them.
  176.  
  177.     2) DATE-TIME REPRESENTATION:
  178.  
  179.     Two representations are currently available: UNIX(R) like and
  180. LOTUS(R) like. The later works with doubles, which means it's slower but
  181. can handle dates from 1900 up to .... . If you redefine BEGINYEAR you'll
  182. be able to deal with other time periods. Nevertheless double values have
  183. plenty of room to hold large periods without overflow.
  184.  
  185.     3) TEST
  186.  
  187.     If you define TEST constant you'll get a nice program to show
  188. you how all this stuff works.
  189.  
  190.     For more info refer to code DEFINES section .
  191.  
  192.     FUNCTIONS
  193.     =========
  194.  
  195.     You have only three functions to care abouth:
  196.  
  197.     1) Sch001DateToNum( ... )
  198.     2) Sch001NumToDate( ... )
  199.     3) Sch001DatCnv( ... )
  200.  
  201.       FUNCTION 1) 
  202.         -----------
  203.  
  204.     Sch001DateToNum(int Day, int Mon, int Yea, int Sec, int Min, int Hou);
  205.  
  206.     Just suply a Day, Month, Year, Second, Minute and Hour and
  207. you'll get a nice time_t as a return value. If you work with LOTUS(R)
  208. representation you'll get a double.
  209.  
  210.       FUNCTION 2)
  211.         -----------
  212.  
  213.     static int    Sch001NumToDate(double Num,
  214.                 int *Day, int *Mon, int *Yea,
  215.                 int *WDay,
  216.                 int *Sec, int *Min, int *Hou
  217.                 );
  218.  
  219.     This function will only be usefull if you use LOTUS(R)
  220. representation. You suply a double and you get in turn the Day, Month,
  221. etc. Remember the integer part of the double represents the number of
  222. days elapsed since 1900 and the fraction represents the time of the day.
  223. Refer to 123 (R) reference manual for further explanations.
  224.  
  225.     FUNCTION 3)
  226.         -----------
  227.  
  228.     UNIX REPRESENTATION
  229.  
  230.     char *Sch001DatCnv(char *Req, long Dat);
  231.  
  232.     LOTUS REPRESENTATION
  233.  
  234.     char *Sch001DatCnv(char *Req, double Dat);
  235.  
  236.     You suply a request string wich can hold any caracters plus any
  237. combination of the following keywords:
  238.     
  239.     KEYWORD        MEANING
  240.         --------------------------------------
  241.     "DD",           Day numeric   
  242.     "HH",              Hour numeric   
  243.     "MI",              Minutes numeric   
  244.     "MM",              Month numeric   
  245.     "YYYY",            Year long figure   
  246.     "YY",          Year short figure   
  247.     "DAY",           Day string   
  248.     "MONTH",         Month string   
  249.     "SHORTMONTH",       Month string short   
  250.     "SS",           Seconds numeric   
  251.     "YEAR",        Year string   
  252.  
  253.     Then you suply a long or double (depends on the model you
  254. choose) and you get a nice string with all your keywords substituted
  255. with their actual values. Example:
  256.  
  257.  
  258.     You request:    Sch001DatCnv("Today is: DD of MONTH, YYYY", 32456,234); 
  259.  
  260.     You get:    "Today is: 09 November 1988"
  261.  
  262.     Nice, isn't it. Have fun ... I'm looking forward to hearing from
  263. you. 
  264.  
  265.  
  266.                                                  John
  267. |                                                                            |
  268. | NOTES                                                                      |
  269. |                                                                            |
  270. |   1) If you ever wish to contact me regarding this source file please      |
  271. |   state the following REFERENCE: 001-890727                                |
  272. |                                                                            |
  273. |   2) This is just a pice of a whole library of C code where all "callable" |
  274. |   functions begin with "Sch" followed by a 3 alphanumeric code.            |
  275. |                                                                            |
  276. |   3) I am willing to cooperate in any software project concerning Medical  |
  277. |   science. I would apreciate any suggestions concerning this possibility.  |
  278. |                                                                            |
  279. | AUTHOR(s)                                                                  |
  280. |                                                                            |
  281. |   John-Marc C. ARNAU                                                       |
  282. |                                                                            |
  283. |   P.O. Box 14208                                                           |
  284. |   08080-BARCELONA (Cathalonia)                                             |
  285. |   EUROPE                                                                   |
  286. |                                                                            |
  287. |   Compuserve: 70441,2164                                                   |
  288. |                                                                            |
  289. | ACKNOWLEDGMENTS                                                            |
  290. |                                                                            |
  291. |   Oliver Laumann, Technical University of Berlin, Germany.                 |
  292. |     For his contribution to converting tm structures to t_time.            |
  293. |                                                                            |
  294. |  Judson D. McClendon                                                       |
  295. |     For WeekDat function.                                                  |
  296. |                                                                            |
  297. |----------------------------------------------------------------------------|
  298. | REVISIONS                                                                  |
  299. |                                                                            |
  300. |                                                                            |
  301. ==============================================================================
  302. */
  303.  
  304. /*
  305. ===========================================
  306. INCLUDE FILES
  307. ===========================================
  308. */
  309.  
  310. #include <time.h>
  311. #include <math.h>
  312. #include <ctype.h>
  313. #include <stdio.h>
  314. #include <stdlib.h>
  315. #include <string.h>
  316.  
  317. /*
  318. ===========================================
  319. DEFINITIONS
  320. ===========================================
  321. */
  322.  
  323. /* Select one language ENGLISH CATHALAN SPANISH*/
  324.  
  325. #define ENGLISH     1
  326.  
  327. /* Select one date-time representation (UNIX_TIM or LOTUS_TIM) */
  328.  
  329. #define LOTUS_TIM 1
  330.  
  331. /* Select TEST if you are willing to test this code */
  332.  
  333. #define TEST      1
  334.  
  335. /*
  336.  *    **************************************************
  337.  *    *                                                *
  338.  *    *              Function Prototypes               *
  339.  *    *                                                *
  340.  *    **************************************************
  341.          ALL LOCAL FUNCTIONS CARRY A STATIC KEYWORD
  342.  */
  343.  
  344.  
  345.  
  346.  
  347. #ifdef UNIX_TIM
  348. time_t         Sch001DateToNum(int Day, int Mon, int Yea,
  349.             int Sec, int Min, int Hou);
  350.  
  351. char         *Sch001DatCnv(char *Req, long Dat);
  352. #endif
  353.  
  354. #ifdef LOTUS_TIM
  355. double         Sch001DateToNum(int Day, int Mon, int Yea,
  356.             int Sec, int Min, int Hou);
  357.  
  358.  
  359. int        Sch001NumToDate(double Num,
  360.             int *Day, int *Mon, int *Yea,
  361.             int *WDay,
  362.             int *Sec, int *Min, int *Hou
  363.             );
  364.  
  365. char         *Sch001DatCnv(char *Req, double Dat);
  366. #endif
  367.  
  368. static int  WeekDay(int Day, int Mon, int Yea);
  369. static char *ShoDay(struct tm *Tim);
  370. static char *ShoMon(struct tm *Tim);
  371. static char *ShoYea(struct tm *Tim);
  372. static char *ShoLonYea(struct tm *Tim);
  373. static char *ShoStrDay(struct tm *Tim);
  374. static char *ShoStrMon(struct tm *Tim);
  375. static char *ShoShortStrMon(struct tm *Tim);
  376. static char *ShoStrYea(struct tm *Tim);
  377. static char *ShoHou(struct tm *Tim);
  378. static char *ShoMin(struct tm *Tim);
  379. static char *ShoSec(struct tm *Tim);
  380.  
  381. /*
  382.  *    **************************************************
  383.  *    *                                                *
  384.  *    *                   Constants                    *
  385.  *    *                                                *
  386.  *    **************************************************
  387.  */
  388.  
  389. #define BEGINYEAR  1900    /* Beginning year */
  390. #define ENDYEAR    5000    /* Ending year    */
  391.  
  392.  
  393.  
  394. /* 
  395. ===========================================
  396. LOCAL DATA
  397. ===========================================
  398. */
  399.  
  400.                            /* Jan Feb Mar Apr May Jun Jul Aug Sep Oct Nov Dec */
  401. static char DaysInMonth[] = { 31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31 };
  402.  
  403. static char *month[] = {
  404. #ifdef ENGLISH
  405.        "January",
  406.        "February",
  407.        "March",
  408.        "April",
  409.        "May",
  410.        "June",
  411.        "July",
  412.        "August",
  413.        "September",
  414.        "October",
  415.        "November",
  416.        "December"
  417. #endif
  418. #ifdef CATHALAN
  419.        "Gener",
  420.        "Febrer",
  421.        "Març",
  422.        "Abril",
  423.        "Maig",
  424.        "Juny",
  425.        "Juliol",
  426.        "Agost",
  427.        "Septembre",
  428.        "Octubre",
  429.        "Novembre",
  430.        "Decembre"       
  431. #endif
  432. #ifdef SPANISH
  433.        "Enero",
  434.        "Febrero",
  435.        "Marzo",
  436.        "Abril",
  437.        "Mayo",
  438.        "Junio",
  439.        "Julio",
  440.        "Agosto",
  441.        "Setiembre",
  442.        "Octubre",
  443.        "Noviembre",
  444.        "Diciembre"
  445. #endif
  446. };
  447.  
  448. static char *ShortMon[] = {
  449. #ifdef ENGLISH
  450.        "Jan",
  451.        "Feb",
  452.        "Mar",
  453.        "Apr",
  454.        "May",
  455.        "Jun",
  456.        "Jul",
  457.        "Aug",
  458.        "Sep",
  459.        "Oct",
  460.        "Nov",
  461.        "Dec"
  462. #endif
  463. #ifdef CATHALAN
  464.        "Gen",
  465.        "Feb",
  466.        "Mar",
  467.        "Abr",
  468.        "Mai",
  469.        "Jun",
  470.        "Jul",
  471.        "Ago",
  472.        "Sep",
  473.        "Oct",
  474.        "Nov",
  475.        "Dec"
  476. #endif
  477. #ifdef SPANISH
  478.        "Ene",
  479.        "Feb",
  480.        "Mar",
  481.        "Abr",
  482.        "May",
  483.        "Jun",
  484.        "Jul",
  485.        "Ago",
  486.        "Set",
  487.        "Oct",
  488.        "Nov",
  489.        "Dic"
  490. #endif
  491. };
  492.  
  493. static char *wkday[] = {
  494. #ifdef ENGLISH
  495.        "Sunday",
  496.        "Monday",
  497.        "Tuesday",
  498.        "Wednesday",
  499.     "Thursday",
  500.        "Friday",
  501.        "Saturday"
  502. #endif
  503. #ifdef SPANISH
  504.        "Domingo",
  505.        "Lunes",
  506.        "Martes",
  507.        "Miercoles",
  508.        "Jueves",
  509.        "Viernes",
  510.        "Sabado"
  511. #endif              
  512. #ifdef CATHALAN
  513.        "Diumenge",
  514.        "Dilluns",       
  515.        "Dimarts",      
  516.        "Dimecres",
  517.        "Dijous",
  518.        "Divendres",
  519.        "Disabte"
  520. #endif
  521. };
  522.  
  523. static char *ShoWeeDay[] = {
  524. #ifdef ENGLISH
  525.        "Sun",
  526.        "Mon",
  527.        "Tue",
  528.        "Wed",
  529.        "Thu",
  530.        "Fri",
  531.        "Sat"
  532. #endif
  533. #ifdef SPANISH
  534.        "Dom",
  535.        "Lun",
  536.        "Mar",
  537.        "Mie",
  538.        "Jue",
  539.        "Vie",       
  540.        "Sab"
  541. #endif       
  542. #ifdef CATHALAN
  543.        "Diu",
  544.        "Dil",
  545.        "Dim",      
  546.        "Die",
  547.        "Dij",
  548.        "Div",
  549.        "Dis"
  550. #endif
  551. };
  552.  
  553. /* Date Time formating keywords */
  554.  
  555. static char *KeyWor[]=
  556. {
  557.  
  558.     "DD",        /* Day numeric */
  559.     "HH",           /* Hour numeric */
  560.     "MI",           /* Minutes numeric */
  561.     "MM",           /* Month numeric */
  562.     "YYYY",         /* Year long figure */
  563.     "YY",       /* Year short figure */
  564.     "DAY",        /* Day string */
  565.     "MONTH",      /* Month string */
  566.     "SHORTMONTH",    /* Month string short */
  567.     "SS",        /* Seconds numeric */
  568.     "YEAR",     /* Year string */
  569.     0
  570. };
  571.  
  572. /* Function pointers associated with above keywords */
  573.  
  574. static char *(* KeyAct [])()=
  575. {
  576.     ShoDay,
  577.     ShoHou,
  578.     ShoMin,
  579.     ShoMon,
  580.     ShoLonYea,
  581.     ShoYea,
  582.     ShoStrDay,
  583.     ShoStrMon,
  584.     ShoShortStrMon,
  585.     ShoSec,
  586.     ShoStrYea,
  587.     0
  588. };
  589.  
  590.  
  591. /*
  592. ===========================================
  593. LOCAL CODE * LEVEL 0
  594. ===========================================
  595. */
  596.  
  597.  
  598. /* Return 1 if `y' is a leap year, 0 otherwise.
  599.  */
  600.  
  601. static int IsLeap(int Yea)
  602. {
  603.     Yea += 1900;
  604.     if (Yea % 400 == 0)
  605.         return (1);
  606.     if (Yea % 100 == 0)
  607.         return (0);
  608.     return (Yea % 4 == 0);
  609. }
  610.  
  611. #ifdef UNIX_TIM
  612.  
  613. /* Return the number of days between Jan 1, 1970 and the given
  614.  * broken-down time.
  615.  */
  616.  
  617. static int ndays (int Day, int Mon, int Yea)
  618. {
  619. register n = Day;
  620. register m, y;
  621.  
  622.     for (y = 70; y < Yea; ++y)
  623.     {
  624.         n += 365;
  625.         if (IsLeap (y)) ++n;
  626.     }
  627.     for (m = 0; m < Mon; ++m)
  628.     n += DaysInMonth[m] + (m == 1 && leap (y));
  629.  
  630.     return (n);
  631. }
  632.  
  633. /* Convert a broken-down time (such as returned by localtime())
  634.  * back into a `time_t'.
  635.  */
  636.  
  637. static time_t Sch001DateToNum(int Day, int Mon, int Yea,
  638.             int Sec, int Min, int Hou
  639.             )
  640. {
  641. register int m1, m2;
  642. time_t t;
  643. struct tm *otm;
  644.  
  645.     t = (ndays (Day, Mon, Yea) - 1) * 86400L + Hou * 3600L
  646.         + Min * 60 + Sec;
  647.  
  648.     /*
  649.     * Now the hard part -- correct for the time zone:
  650.     */
  651.  
  652.  
  653.     otm = localtime (&t);
  654.  
  655.     m2 = Hou * 60 + Min;
  656.     m1 = otm->tm_hour * 60 + otm->tm_min;
  657.     t -= ((m1 - m2 + 720 + 1440) % 1440 - 720) * 60L;
  658.  
  659.     return (t);
  660. }
  661.  
  662. #endif
  663.  
  664. #ifdef LOTUS_TIM
  665.  
  666. static int WeekDay(int Day, int Mon, int Yea)
  667.  
  668. {
  669.  
  670.     if (Mon < 3)
  671.     {
  672.         Yea -= 1;
  673.         Mon += 12;
  674.     }
  675.  
  676.     return( (Day + 1
  677.         + (2 * Mon)
  678.         + ((Mon + 1) * 3 / 5)
  679.         + (Yea)
  680.         + (Yea / 4)
  681.         - (Yea / 100)
  682.         + (Yea / 400)
  683.         ) % 7);
  684.  
  685. }
  686.  
  687.  
  688.  
  689. static double Sch001DateToNum(int Day, int Mon, int Yea,
  690.             int Sec, int Min, int Hou
  691.             )
  692. {
  693. int    Cnt;
  694. long    Ret;
  695. double    GloRet = 0.0;
  696.  
  697.     for(Cnt = BEGINYEAR, Ret = 0; Cnt < Yea; Cnt++)
  698.     {
  699.           if ((Cnt % 400) == 0)
  700.              Ret += 366;
  701.           else if ((Cnt % 100) == 0)
  702.              Ret += 365;
  703.           else if ((Cnt % 4) == 0)
  704.          Ret += 366;
  705.           else
  706.              Ret += 365;
  707.     }
  708.  
  709.     if ((Yea % 400) == 0)
  710.         DaysInMonth[1] = 29;
  711.     else if ((Yea % 100) == 0)
  712.         DaysInMonth[1] = 28;
  713.     else if ((Yea % 4) == 0)
  714.         DaysInMonth[1] = 29;
  715.     else
  716.         DaysInMonth[1] = 28;
  717.  
  718.     for(Cnt = 0; Cnt < Mon; Cnt++)
  719.     {
  720.              Ret += DaysInMonth[Cnt];
  721.     }
  722.  
  723.     Ret += Day + 1;
  724.  
  725.     /* Compute sec min hou */
  726.     GloRet =     Hou / 24.0;
  727.     GloRet +=     Min / (24.0 * 60.0);
  728.     GloRet +=     Sec / (24.0 * 60.0 * 60.0);
  729.  
  730.     GloRet += (double)Ret;
  731.     return((double) GloRet);
  732. }
  733.  
  734.  
  735. static int    Sch001NumToDate(double Num,
  736.             int *Day, int *Mon, int *Yea,
  737.             int *WDay,
  738.             int *Sec, int *Min, int *Hou
  739.             )
  740. {
  741. int    Cnt;
  742. long    Ret;
  743. long     Goal;
  744. double  Tim, Dummy;
  745.  
  746.     Goal = (long)Num;
  747.     Tim  = modf(Num, &Dummy);
  748.  
  749.     /* Compute Yea Mon Day */
  750.  
  751.     for(Cnt = BEGINYEAR, Ret = 0; Ret < Goal; Cnt++)
  752.     {
  753.           if ((Cnt % 400) == 0)
  754.              Ret += 366;
  755.           else if ((Cnt % 100) == 0)
  756.              Ret += 365;
  757.           else if ((Cnt % 4) == 0)
  758.          Ret += 366;
  759.           else
  760.              Ret += 365;
  761.     }
  762.  
  763.     Cnt--;
  764.     *Yea = Cnt;
  765.  
  766.     if ((Cnt % 400) == 0)
  767.     {
  768.         Ret -= 366;
  769.         DaysInMonth[2] = 29;
  770.     }
  771.     else if ((Cnt % 100) == 0)
  772.     {
  773.         Ret -= 365;
  774.         DaysInMonth[1] = 28;
  775.     }
  776.     else if ((Cnt % 4) == 0)
  777.     {
  778.         Ret -= 366;
  779.         DaysInMonth[1] = 29;
  780.     }
  781.     else
  782.     {
  783.         Ret -= 365;
  784.         DaysInMonth[1] = 28;
  785.     }
  786.  
  787.     for(Cnt = 0; Ret < Goal; Cnt++)
  788.     {
  789.              Ret += DaysInMonth[Cnt];
  790.     }
  791.     Cnt--;
  792.     *Mon = Cnt;
  793.  
  794.     Ret -= DaysInMonth[Cnt];
  795.  
  796.     *Day = (int)(Goal - Ret - 1);
  797.  
  798.     /* Compute week day */
  799.  
  800.     *WDay = WeekDay(*Day, *Mon, *Yea);
  801.  
  802.     /* Compute hour min and sec */
  803.  
  804.     Dummy     = Tim * 24.0;
  805.     *Hou     = (int)Dummy;
  806.     Tim    = modf(Dummy, &Dummy);
  807.     Dummy    = Tim * 60;
  808.     *Min    = (int)Dummy;
  809.     Tim    = modf(Dummy, &Dummy);
  810.     Dummy    = Tim * 60;
  811.     *Sec    = (int)Dummy;
  812.     *Sec     += 1;
  813.     return(0);
  814. }
  815. #endif
  816.  
  817. /*
  818. ===========================================
  819. LOCAL CODE * LEVEL 1
  820. ===========================================
  821. */
  822.  
  823. static char *ShoDay(Tim)
  824. struct tm *Tim;
  825. {
  826. static     char         TmpBuf[18];
  827.  
  828.     sprintf(TmpBuf, "%02d", Tim->tm_mday);
  829.     return(TmpBuf);
  830. }
  831.  
  832. static char *ShoMon(Tim)
  833. struct tm *Tim;
  834. {
  835. static     char         TmpBuf[18];
  836.  
  837.     sprintf(TmpBuf, "%02d", Tim->tm_mon + 1);
  838.     return(TmpBuf);
  839. }
  840.  
  841. static char *ShoYea(Tim)
  842. struct tm *Tim;
  843. {
  844. static     char         TmpBuf[18];
  845.  
  846. #ifdef UNIX_TIM
  847.     sprintf(TmpBuf, "%02d", Tim->tm_year);
  848. #endif
  849. #ifdef LOTUS_TIM
  850.     sprintf(TmpBuf, "%02d", Tim->tm_year-BEGINYEAR);
  851. #endif
  852.  
  853.     return(TmpBuf);
  854. }
  855.  
  856. static char *ShoLonYea(Tim)
  857. struct tm *Tim;
  858. {
  859. static     char         TmpBuf[18];
  860.  
  861. #ifdef UNIX_TIM
  862.     sprintf(TmpBuf, "%02d%02d",
  863.         Tim->tm_year > 70 ? 19: 20,
  864.         Tim->tm_year);
  865. #endif
  866. #ifdef LOTUS_TIM
  867.     sprintf(TmpBuf, "%04d", Tim->tm_year);
  868. #endif
  869.  
  870.     return(TmpBuf);
  871. }
  872.  
  873. static char *ShoStrDay(Tim)
  874. struct tm *Tim;
  875. {
  876. static     char         TmpBuf[18];    
  877.  
  878.     sprintf(TmpBuf, "%s",
  879.         wkday[Tim->tm_wday]);
  880.     return(TmpBuf);
  881. }
  882.  
  883. static char *ShoStrMon(Tim)
  884. struct tm *Tim;
  885. {
  886. static     char         TmpBuf[18];
  887.  
  888.     sprintf(TmpBuf, "%s",
  889.         month[Tim->tm_mon]);
  890.     return(TmpBuf);
  891. }
  892.  
  893. static char *ShoShortStrMon(Tim)
  894. struct tm *Tim;
  895. {
  896. static     char         TmpBuf[18];
  897.  
  898.     sprintf(TmpBuf, "%s",
  899.         ShortMon[Tim->tm_mon]);
  900.     return(TmpBuf);
  901. }
  902.  
  903. static char *ShoStrYea(Tim)
  904. struct tm *Tim;
  905. {
  906. static     char         TmpBuf[18];
  907.  
  908.     strcpy(TmpBuf, "NOT AVAILABLE YET");         
  909.     return(TmpBuf);
  910. }
  911.  
  912.  
  913. static char *ShoHou(Tim)
  914. struct tm *Tim;
  915. {
  916. static     char         TmpBuf[18];
  917.  
  918.     sprintf(TmpBuf, "%02d", Tim->tm_hour);
  919.     return(TmpBuf);
  920. }
  921.  
  922. static char *ShoMin(Tim)
  923. struct tm *Tim;
  924. {
  925. static     char         TmpBuf[18];
  926.  
  927.     sprintf(TmpBuf, "%02d", Tim->tm_min);
  928.     return(TmpBuf);
  929. }
  930.  
  931. static char *ShoSec(Tim)
  932. struct tm *Tim;
  933. {
  934. static     char         TmpBuf[18];
  935.  
  936.     sprintf(TmpBuf, "%02d", Tim->tm_sec);
  937.     return(TmpBuf);
  938. }
  939.  
  940. /*
  941. ===========================================
  942. FUNCTION
  943. ===========================================
  944. */
  945.  
  946. #ifdef UNIX_TIM
  947. char *Sch001DatCnv(char *Req, long Dat)
  948. #endif
  949.  
  950. #ifdef LOTUS_TIM
  951. char *Sch001DatCnv(char *Req, double Dat)
  952. #endif
  953.  
  954. {
  955. static     char         Res[100];
  956.     char         *ReqPtr, *ResPtr;
  957.     char        TmpBuf[100];
  958.     int        Cnt, Ski;
  959.     long         Clk;
  960. #ifdef UNIX_TIM
  961.     struct tm     *Tim;
  962. #endif
  963. #ifdef LOTUS_TIM
  964.     struct tm     Tim;
  965. #endif
  966.  
  967.  
  968.  
  969. #ifdef UNIX_TIM
  970.        Tim = localtime(&Dat);
  971. #endif
  972.  
  973. #ifdef LOTUS_TIM
  974.     Sch001NumToDate(Dat,
  975.         &Tim.tm_mday, &Tim.tm_mon, &Tim.tm_year,
  976.         &Tim.tm_wday,
  977.         &Tim.tm_sec, &Tim.tm_min, &Tim.tm_hour
  978.         );
  979. #endif
  980.  
  981.     ReqPtr = Req;
  982.     ResPtr = Res;
  983.  
  984.     while(*ReqPtr)
  985.     {
  986.         for(Ski = 0, Cnt = 0; KeyWor[Cnt]; Cnt++)
  987.         {
  988.             if(!strncmp(KeyWor[Cnt], ReqPtr, strlen(KeyWor[Cnt])))
  989.             {
  990. #ifdef UNIX_TIM                
  991.                 strcpy(TmpBuf, (* KeyAct[Cnt])(Tim));
  992. #endif
  993. #ifdef LOTUS_TIM
  994.                 strcpy(TmpBuf, (* KeyAct[Cnt])(&Tim));
  995. #endif
  996.                 strcpy(ResPtr, TmpBuf);
  997.                 ReqPtr += strlen(KeyWor[Cnt]);
  998.                 ResPtr += strlen(TmpBuf);
  999.                 Ski    = 1;
  1000.             }
  1001.         }
  1002.  
  1003.         if(!Ski)
  1004.             *ResPtr++ = *ReqPtr++;
  1005.     }
  1006.     ResPtr++;
  1007.     *ResPtr = '\0';
  1008.     return(Res);
  1009. }
  1010.  
  1011.  
  1012. /*
  1013. ===========================================
  1014. TEST CODE
  1015. ===========================================
  1016. */
  1017.  
  1018. #ifdef TEST
  1019. main()
  1020. {
  1021. char    Tpl[100];    /* Template */
  1022.  
  1023. #ifdef UNIX_TIM
  1024. long     Dat;
  1025. struct tm     *Tim;
  1026. #endif
  1027.  
  1028. #ifdef LOTUS_TIM
  1029. double    Dat;
  1030. struct tm     Tim;
  1031. #endif
  1032.  
  1033.     printf("***Schön Date-Time Handling system***\n");
  1034.     printf("(c)1989 SchönSoft & John-Marc C. Arnau\n");
  1035.  
  1036.     printf("Template ?: ");
  1037.     scanf("%[^\n]", Tpl);
  1038.     printf("Date ....?: ");
  1039.  
  1040. #ifdef UNIX_TIM
  1041.     scanf("%ld", &Dat);
  1042. #endif
  1043.  
  1044. #ifdef LOTUS_TIM
  1045.     scanf("%lg", &Dat);
  1046. #endif
  1047.  
  1048.     printf("Result ...: %s\n", Sch001DatCnv(Tpl, Dat));
  1049.  
  1050. #ifdef LOTUS_TIM
  1051.     Sch001NumToDate(Dat,
  1052.         &Tim.tm_mday, &Tim.tm_mon, &Tim.tm_year,
  1053.         &Tim.tm_wday,
  1054.         &Tim.tm_sec, &Tim.tm_min, &Tim.tm_hour
  1055.         );
  1056.     Dat = Sch001DateToNum(Tim.tm_mday, Tim.tm_mon, Tim.tm_year,
  1057.         Tim.tm_sec, Tim.tm_min, Tim.tm_hour
  1058.         );
  1059.     printf("Rev. TEST : %5.6lg\n",
  1060.         Dat);
  1061. #endif
  1062.  
  1063. #ifdef UNIX_TIM
  1064.     Tim = localtime(&Dat);
  1065.     Dat = Sch001DateToNum(Tim->tm_mday, Tim->tm_mon, Tim->tm_year,
  1066.         Tim->tm_sec, Tim->tm_min, Tim->tm_hour
  1067.         );
  1068.     printf("Rev. TEST : %ld\n",
  1069.         Dat);
  1070.  
  1071. #endif
  1072.  
  1073.     printf("******** END OF TEST ***********\n");
  1074.     printf("Press CR to end\n");
  1075.     getchar();
  1076.     getchar();
  1077. }
  1078. #endif
  1079.  
  1080.